package de.ret_world.openrpgstudio.eventengine.scripts;

import de.ret_world.openrpgstudio.editor.script.Point;
import de.ret_world.openrpgstudio.editor.script.ScriptObject;
import de.ret_world.openrpgstudio.engine.artemis.components.Location;
import java.util.HashMap;
import org.luaj.vm2.LuaTable;
import org.luaj.vm2.LuaValue;
import org.luaj.vm2.Varargs;

/**
 *
 * @author Emu
 */
public class Event implements ScriptObject {

    public static final String TYPE = "Event";
    private String ID;
    private LuaValue updateFunction = null;
    private LuaValue actionFunction = null;
    private Location location = new Location("---", "---", new Point(0, 0));
    private String skin = "";
    private String notes = "";
    private HashMap<String, String> tags = new HashMap<>();

    @Override
    public void create(LuaValue val) {
        if (!val.get("id").isnil()) {
            ID = val.get("id").toString();
        }
        if (!val.get("notes").isnil()) {
            notes = val.get("notes").toString();
        }
        if (!val.get("update").isnil()) {
            updateFunction = val.get("update");
        }
        if (!val.get("action").isnil()) {
            actionFunction = val.get("action");
        }
        if (!val.get("location").isnil() && val.get("location").istable()) {
            LuaValue loc = val.get("location");
            String map = null, layer = null;
            int x = 0, y = 0;

            if (!loc.get("map").isnil()) {
                map = val.get("map").toString();
            }
            if (!loc.get("layer").isnil()) {
                layer = val.get("layer").toString();
            }
            if (!loc.get("x").isnil()) {
                x = val.get("x").toint();
            }
            if (!loc.get("y").isnil()) {
                y = val.get("y").toint();
            }

            location = new Location(map, layer, new Point(x, y));
        }
        if (!val.get("skin").isnil()) {
            skin = val.get("skin").toString();
        }
        if (!val.get("tags").isnil()) {
            if (val.get("tags").istable()) {
                tags.clear();
                LuaValue k = LuaValue.NIL;
                while (true) {
                    Varargs n = val.get("tags").next(k);
                    if ((k = n.arg1()).isnil()) {
                        break;
                    }
                    LuaValue v = n.arg(2);
                    tags.put(k.toString(), v.toString());
                }
            }
        }
    }

    @Override
    public LuaTable toLua() {
        LuaTable lua = new LuaTable();
        lua.set("id", LuaTable.valueOf(ID));

        LuaTable loc = new LuaTable();
        loc.set("map", location.getMapID());
        loc.set("layer", location.getLayerID());
        loc.set("x", location.getPoint().getX());
        loc.set("y", location.getPoint().getY());
        lua.set("location", loc);

        lua.set("skin", LuaTable.valueOf(skin));
        lua.set("notes", LuaTable.valueOf(notes));

        LuaTable ltags = new LuaTable();
        for (String k : tags.keySet()) {
            ltags.set(LuaTable.valueOf(k), LuaTable.valueOf(tags.get(k)));
        }
        lua.set("tags", ltags);

        lua.set("update", updateFunction);
        lua.set("action", actionFunction);

        return lua;
    }

    @Override
    public String toScript() {
        String s = "event = {} -- init new event\n"
                + "event.id = '" + ID + "'\n"
                + "event.location = {}\n"
                + "event.location.map = '" + location.getMapID() + "'\n"
                + "event.location.layer = '" + location.getLayerID() + "'\n"
                + "event.location.x = " + location.getPoint().getX() + "\n"
                + "event.location.y = " + location.getPoint().getY() + "\n"
                + "event.skin = '" + skin + "'\n"
                + "event.notes = [[" + notes + "]]\n"
                + "event.tags = {}\n";

        for (String k : tags.keySet()) {
            s += "event.tags['" + k + "'] = '" + tags.get(k) + "'\n";
        }

        return s;
    }

    public String getID() {
        return ID;
    }

    public void setID(String ID) {
        this.ID = ID;
    }

    public LuaValue getUpdateFunction() {
        return updateFunction;
    }

    public void setUpdateFunction(LuaValue updateFunction) {
        this.updateFunction = updateFunction;
    }

    public LuaValue getActionFunction() {
        return actionFunction;
    }

    public void setActionFunction(LuaValue actionFunction) {
        this.actionFunction = actionFunction;
    }

    public Location getLocation() {
        return location;
    }

    public void setLocation(Location location) {
        this.location = location;
    }

    public String getSkin() {
        return skin;
    }

    public void setSkin(String skin) {
        this.skin = skin;
    }

    public String getNotes() {
        return notes;
    }

    public void setNotes(String notes) {
        this.notes = notes;
    }

    public HashMap<String, String> getTags() {
        return tags;
    }

    public void setTags(HashMap<String, String> tags) {
        this.tags = tags;
    }

    @Override
    public String toString() {
        return ID;
    }
}
